//
//  GameMatrixSQLite.cpp
//  Chart
//
//  Created by CaoJun on 13-11-6.
//
//

#include "GameMatrixSQLite.h"
#include "YTXChartTools.h"

using namespace ytx;
using namespace std;

GameMatrixSQLite::GameMatrixSQLite() : BaseSQLite(){
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *documentsDirectory = paths[0];
    NSString *fileName = [NSString stringWithFormat:@"%@/GameMatrixData.rdb", documentsDirectory];
    path = [fileName UTF8String];
}

GameMatrixSQLite::~GameMatrixSQLite(){
    sqlite3_close(sqliteDB);
}

//bool GameMatrixSQLite::checkInRange(string tableName, YTXTime * outputLastTime, GameMatrix * gm, YTXTime time)
//{
//    if(openDB())
//    {
//        DBResult dbResult;
//        dbResult.status = false;
//        char * errmsg = 0;
//        const string queryStr = "SELECT date FROM "+ tableName+" ORDER BY date DESC LIMIT 0,1";
//        int ret = sqlite3_exec(sqliteDB, queryStr.c_str(), BaseSQLite::handelr_exec, &dbResult, &errmsg);
//        CheckResult(ret, errmsg);
//        CheckDBResult(dbResult, "checkInRange");
//        string tempTime = dbResult.getValue(0,0);
//        
//        long latestValue = Tools::parseLong(tempTime);
//        
//        YTXTime lastestTime = YTXTime(latestValue);
//        
//        (*outputLastTime) = lastestTime;
//
////        NSLog(@"GameMatrixSQLite.checkInRange lastestTime:%@", [NSString stringWithUTF8String:lastestTime.toStringYYYYMMddHHmmss().c_str()] );
////        NSLog(@"GameMatrixSQLite.checkInRange tradeDate:%@", [NSString stringWithUTF8String: tradeDate.toStringYYYYMMddHHmmss().c_str() ]);
//        
//        sqlite3_close(sqliteDB);
//        return gm->isInLatestNewK(lastestTime, time);
//    }
//    sqlite3_close(sqliteDB);
//    return false;
//}

bool GameMatrixSQLite::getDataFromDB(string tableName,YTXTime time, vector<GameMatrixItem> * gmItems, const unsigned int limit)
{
    if(openDB())
    {
        DBResult dbResult;
        dbResult.status = false;
        char * errmsg = 0;
        const string queryStr = "SELECT * FROM "+ tableName+" WHERE tradedate<"+ ConvertToString( time.getCurrentTime() ) +" ORDER BY tradedate DESC LIMIT 0,"+ConvertToString(limit);
        int ret = sqlite3_exec(sqliteDB, queryStr.c_str(), BaseSQLite::handelr_exec, &dbResult, &errmsg);
        CheckResult(ret, errmsg);
        CheckDBResult(dbResult, "getDataFromDB");
        (*gmItems) = transforDataGameMatrixItem(dbResult);
        sqlite3_close(sqliteDB);
        return true;
        
    }
    sqlite3_close(sqliteDB);
    return false;
}

vector<GameMatrixItem> GameMatrixSQLite::transforDataGameMatrixItem(DBResult & dbResult)
{
    vector<GameMatrixItem> result;

    double bound1,bound2;
    GameMatrixType::GameMatrixType type;
    YTXTime tradedate;
    unsigned int index = 0;
    unsigned int size = (unsigned int)(dbResult.row_value.size() - 1);
    //有多少列是确定的
    for (vector<vector <string> >::reverse_iterator it =  dbResult.row_value.rbegin(); it != dbResult.row_value.rend(); ++it) {
        index = size - (unsigned int)(it-dbResult.row_value.rbegin());
        tradedate = YTXTime( Tools::parseLong( dbResult.getValue(index, 0) ) );
        type = (GameMatrixType::GameMatrixType)Tools::parseInt( dbResult.getValue(index, 1) );
        bound1 = Tools::parseDouble( dbResult.getValue(index, 2) );
        bound2 = Tools::parseDouble( dbResult.getValue(index, 3) );
        
        GameMatrixItem gm = {
            tradedate,
            type,
            bound1,
            bound2,
        };
        
        result.push_back(gm);
    }
    
    return result;
}


bool GameMatrixSQLite::insertData(string tableName, vector<GameMatrixItem> data)
{
    if (openDB())
    {
        char * errmsg = 0;
        sqlite3_exec(sqliteDB, "begin;", 0, 0, 0);

        for (vector<GameMatrixItem>::iterator iter = data.begin() ; iter != data.end() ; iter++ )
        {
            GameMatrixItem data = (*iter);
            const string sqlStr = "INSERT INTO "+ tableName +" (tradedate, type, bound1, bound2) VALUES("+ ConvertToString(data.tradedate.getCurrentTime()) + "," + ConvertToString(data.type)+","+ ConvertToString(data.bound1)+","+ ConvertToString(data.bound2) +")";
            int ret = sqlite3_exec(sqliteDB, sqlStr.c_str(), 0, 0, &errmsg);
            ContinueResult(ret, errmsg);
        }
        sqlite3_exec(sqliteDB, "commit;", 0, 0, 0);
        sqlite3_close(sqliteDB);
        return true;
    }
    return false;
}

bool GameMatrixSQLite::createKLineDataTableIfNotExit(const string tableName)
{
    //    sqlite3_stmt *stmt = NULL;
//    sqlite3 * sqliteDB = getDB(path, false);
    if (openDB()){
        char * errmsg = 0;
        int ret;
        const string hasTbaleSQL = "SELECT COUNT(*) FROM sqlite_master where type='table' AND name='"+tableName+"'";

        DBResult dbResult;
        dbResult.status = false;

        ret = sqlite3_exec(sqliteDB,hasTbaleSQL.c_str(), BaseSQLite::handelr_exec, &dbResult, &errmsg);

        CheckResult(ret, errmsg);

        if (Tools::parseInt(dbResult.getValue(0, 0)) > 0) {
//            sqlite3_close(sqliteDB);
            return true;
        }

        const string createTableSQL =
            "CREATE TABLE "+ tableName +" (\
            tradedate INTEGER PRIMARY KEY NOT NULL UNIQUE,\
            type REAL,\
            bound1 REAL,\
            bound2 REAL\
        )";

        ret = sqlite3_exec(sqliteDB,createTableSQL.c_str(), handelr_exec, &dbResult, &errmsg);

        CheckResult(ret, errmsg);

//        sqlite3_close(sqliteDB);
        return true;
    }

    sqlite3_close(sqliteDB);
    return false;
}

bool GameMatrixSQLite::vacuumDB()
{
    if (openDB())
    {
        char * errmsg = 0;
        int ret;
        const string hasTbaleSQL = "VACUUM";
        
        DBResult dbResult;
        dbResult.status = false;
        
        ret = sqlite3_exec(sqliteDB,hasTbaleSQL.c_str(), BaseSQLite::handelr_exec, &dbResult, &errmsg);
        
        CheckResult(ret, errmsg);
        return true;
    }
    sqlite3_close(sqliteDB);
    return false;
}